//work for tomorrow: write again library for curve.

var canvas = new fabric.Canvas('black_board_buffer');

canvas.observe({
    'object:selected': onObjectSelected,
    'object:moving': onObjectMoving,
    'before:selection:cleared': onBeforeSelectionCleared,
    'selection:created': onSelectionCreated,
    'object:over': onObjectOver,
});

drawQuadratic = function (point0, point1, point2) {

	var x_max = Math.max(point0.x, point1.x, point2.x),
		x_min = Math.min(point0.x, point1.x, point2.x),
		y_max = Math.max(point0.y, point1.y, point2.y),
		y_min = Math.min(point0.y, point1.y, point2.y);
	
	var width = x_max - x_min,
		height = y_max - y_min;
	
    var line = new fabric.Path('M 0 0 Q 0, 0, 0, 0', {
    	width: width,
    	height: height,
    	top: y_min + height/2,
    	left: x_min + width/2,
        fill: '',
        stroke: 'black'
    });
    
    line.hasBorders = false;
    line.hasControls = false;
    line.selectable = true;
    line.name = 'sgl_path';
    
    line.path[0][1] = point0.x - x_min; //100
    line.path[0][2] = point0.y - y_min; //100
    line.path[1][3] = point1.x - x_min; //300;
    line.path[1][4] = point1.y - y_min; //100;
    line.path[1][1] = point2.x - x_min; //200;
    line.path[1][2] = point2.y - y_min; //200;
    
    line.point0 = point0;
    line.point1 = point1;
    line.point2 = point2;
    
    var p2 = makeCurvePoint(point2.x, point2.y, line)
    p2.name = "p2";
    canvas.add(p2);

    var p0 = makeCurveCircle(point0.x, point0.y, line);
    p0.name = "p0";
    canvas.add(p0);

    var p1 = makeCurveCircle(point1.x, point1.y, line);
    p1.name = "p1";
    canvas.add(p1);
    
    line.p0 = p0;
    line.p1 = p1;
    line.p2 = p2;
    canvas.add(line);

    function makeCurveCircle(left, top, line) {
        var c = new fabric.Circle({
            left: left,
            top: top,
            strokeWidth: 1,
            radius: 2,
            fill: 'none',
            stroke: '#666'
        });

        c.hasBorders = true
        c.hasControls = false;
        c.line = line;

        return c;
    }

    function makeCurvePoint(left, top, line) {
        var c = new fabric.Circle({
            left: left,
            top: top,
            strokeWidth: 2,
            radius: 3,
            fill: 'none',
            stroke: '#666'
        });

        c.hasBorders = true
        c.hasControls = false;

        c.line = line;
        
        return c;
    }
};

function onObjectSelected(e) {
    var p = e.memo.target;
    
    if(p.name == 'sgl_path')
    {
    	console.log(p);
    	p.setActive(false);
    	
    	toogleAllControl(p, '1')
    	
    	canvas.renderAll();
    }
}

function toogleAllControl(oPath, iDisplay)
{
	oPath.p0.animate('opacity', iDisplay, {
        duration: 200,
        onChange: canvas.renderAll.bind(canvas)
    });
	oPath.p1.animate('opacity', iDisplay, {
        duration: 200,
        onChange: canvas.renderAll.bind(canvas)
    });
	oPath.p2.animate('opacity', iDisplay, {
        duration: 200,
        onChange: canvas.renderAll.bind(canvas)
    });
}

function onBeforeSelectionCleared(e) {
	var p = e.memo.target;
    
	console.log(p);
	var aSelectObject = ['sgl_path', 'p0', 'p1', 'p2'];
	
    if(jQuery.inArray(p.name, aSelectObject) >= 0)
    {
    	if(p.name == 'sgl_path')
    		toogleAllControl(p, '0');
    	else
    		toogleAllControl(p.line, '0');
    }
    /*if (activeObject.name == "p0" || activeObject.name == "p2") {
        activeObject.line2.animate('opacity', '0', {
            duration: 200,
            onChange: canvas.renderAll.bind(canvas)
        });
        activeObject.line2.selectable = false;
    } else if (activeObject.name == "p1") {
        activeObject.animate('opacity', '0', {
            duration: 200,
            onChange: canvas.renderAll.bind(canvas)
        });
        activeObject.selectable = false;
    }*/
}

function onObjectOver(e){
	var p = e.memo.target;
	console.log(e);
}

function onSelectionCreated(e){
	var p = e.memo.target;
	if(p.objects && p.objects.length > 0)
	{
		for(var i = 0; i < p.objects.length; i++)
		{
			if(p.objects[i].name == "p0" || p.objects[i].name == "p2" || p.objects[i].name == "p1")
			{
				p.remove(p.objects[i]);
				i--;
			}
		}
	}
}

function reCalcPathObject(oPath, sObjectMove, iLeft, iTop){
	if(sObjectMove == 'p0'){
		oPath.point0 = new fabric.Point(iLeft, iTop);
	} else if(sObjectMove == 'p1'){
		oPath.point1 = new fabric.Point(iLeft, iTop);
	} else if(sObjectMove == 'p2'){
		oPath.point2 = new fabric.Point(iLeft, iTop);
	}
	
	var point0 = oPath.point0,
		point1 = oPath.point1,
		point2 = oPath.point2;
	
	var x_max = Math.max(point0.x, point1.x, point2.x),
		x_min = Math.min(point0.x, point1.x, point2.x),
		y_max = Math.max(point0.y, point1.y, point2.y),
		y_min = Math.min(point0.y, point1.y, point2.y);

	var width = x_max - x_min,
		height = y_max - y_min;
	
	oPath.set({
		'width': width, 
		'height': height,
		'top': y_min + height/2,
		'left': x_min + width/2
	});
	
	oPath.path[0][1] = point0.x - x_min; //100
	oPath.path[0][2] = point0.y - y_min; //100
	oPath.path[1][3] = point1.x - x_min; //300;
	oPath.path[1][4] = point1.y - y_min; //100;
	oPath.path[1][1] = point2.x - x_min; //200;
	oPath.path[1][2] = point2.y - y_min; //200;
	canvas.renderAll();
}

function onObjectMoving(e) {
	var p = e.memo.target;
	if(p.name == 'p0')
	{
        reCalcPathObject(p.line, 'p0', p.left, p.top);
	}
	else if(p.name == 'p2')
	{
        reCalcPathObject(p.line, 'p2', p.left, p.top);
	}
	else if (p.name == "p1") {
        reCalcPathObject(p.line, 'p1', p.left, p.top);
    }
	else if (p.name == 'sgl_path') {
		console.log('dang di chuyen em no');
		console.log(e.memo.target);
	}
	
}

jQuery(document).ready(function () {
    var p0 = new fabric.Point(100, 100);
    var p1 = new fabric.Point(400, 100);
    var p2 = new fabric.Point(300, 200);
    drawQuadratic(p0, p1, p2);
});